package com.durablemethods.futures.client;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.i18n.client.DateTimeFormat;
import com.google.gwt.user.client.Timer;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.Anchor;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.DialogBox;
import com.google.gwt.user.client.ui.DisclosurePanel;
import com.google.gwt.user.client.ui.FlexTable;
import com.google.gwt.user.client.ui.HorizontalPanel;
import com.google.gwt.user.client.ui.Image;
import com.google.gwt.user.client.ui.Label;
import com.google.gwt.user.client.ui.ListBox;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.TextBox;
import com.google.gwt.user.client.ui.VerticalPanel;


/**
 * Entry point classes define <code>onModuleLoad()</code>.
 */
public class DurableFutures implements EntryPoint {
	private static final int REFRESH_MARKET_INTERVAL = 6000;
	private LoginInfo loginInfo = null;
	private VerticalPanel mainPanel;
	private FlexTable marketFlexTable = new FlexTable();
	private VerticalPanel loginPanel = new VerticalPanel();
	private HorizontalPanel marketPanel = new HorizontalPanel();
	private Label loginLabel = new Label("Please sign in to your Google Account to access the Durable Futures Exchange");
	private Anchor signInLink = new Anchor("Sign In Please");
	private Anchor signOutLink = new Anchor("Sign Out");
	private Label welcomeLabel = new Label("");
	private NHLMarketsServiceAsync nhlMarketService = GWT.create(NHLMarketsService.class);
	private NHLTeamServiceAsync nhlTeamService = GWT.create(NHLTeamService.class);
	private List<NHLTeam> allTeams = new ArrayList<NHLTeam>();
	private List<String> eastTeamIds = new ArrayList<String>();
	private Label lastUpdatedLabel = new Label();
	private ListBox teams;
	private ListBox traders;
	private NHLTrader trader;
	private NHLTraderServiceAsync nhlTraderServiceAsync = GWT.create(NHLTraderService.class);
	private NHLTraderPositionServiceAsync nhlTraderPositionService = GWT.create(NHLTraderPositionService.class);
	private ListBox buySell;
	private TextBox sharesBox;
	private TextBox priceBox;
	private Map<String, NHLTrader> traderMap = new HashMap<String,NHLTrader>();
	private Button tradeButton;
	private Label blockTradeLabel = new Label("");
	private FlexTable positionTable = new FlexTable();
	private FlexTable myMarketsTable = new FlexTable();
	private Anchor temsportsMarketAnchor = new Anchor("TEM Sports Market","http://www.temsportsmarket.com","_blank");
	private Button refreshMyMarketsButton; 
	
	  

	@Override
	public void onModuleLoad() {
		LoginServiceAsync loginService = GWT.create(LoginService.class);
	    loginService.login(GWT.getHostPageBaseURL(), new AsyncCallback<LoginInfo>() {
	      public void onFailure(Throwable error) {
	      }

	      public void onSuccess(LoginInfo result) {
	        loginInfo = result;
	        if(loginInfo.isLoggedIn()) {
	        	createMarket();
	        } else {
	          loadLogin();
	        }
	      }
	    });
		
	}
	public void loadLogin(){
		 // Assemble login panel.
	    signInLink.setHref(loginInfo.getLoginUrl());
	    loginPanel.add(loginLabel);
	    loginPanel.add(signInLink);
	    loginPanel.add(temsportsMarketAnchor);
	    
	    RootPanel.get("marketList").add(loginPanel);
	}

	private void createMarket() {
		mainPanel = new VerticalPanel();
		mainPanel.add(signOutLink);
		signOutLink.setHref(loginInfo.getLogoutUrl());
		mainPanel.add(welcomeLabel);
		marketFlexTable.addStyleName("marketTable");
		marketFlexTable.getRowFormatter().addStyleName(0, "watchListHeader");
		marketFlexTable.setText(0, 0, "");
		marketFlexTable.setText(0, 1, "Product");
		marketFlexTable.setText(0, 2, "Hub");
		marketFlexTable.setText(0, 3, "Sell");
		marketFlexTable.setText(0, 4, "Qty");
		marketFlexTable.setText(0, 5, "Bid");
		marketFlexTable.setText(0, 6, "Offer");
		marketFlexTable.setText(0, 7, "Qty");
		marketFlexTable.setText(0, 8, "Buy");
		marketFlexTable.setText(0, 9, "Last");
		marketFlexTable.setText(0, 10, "POS");
		
//		positionTable.setText(0,0,"");
//		positionTable.getRowFormatter().addStyleName(0, "watchListHeader");
//		positionTable.setText(0,1,"Team");
//		positionTable.setText(0,2,"Position");

		myMarketsTable.getRowFormatter().addStyleName(0, "watchListHeader");
		myMarketsTable.setText(0, 0, "Kill");
		myMarketsTable.setText(0, 1, "b/o");
		myMarketsTable.setText(0, 2, "Team");
		myMarketsTable.setText(0, 3, "Level");
		myMarketsTable.setText(0, 4, "Volume");
		
		refreshMyMarketsButton = new Button("Refresh my Markets", new ClickHandler() {
			
			@Override
			public void onClick(ClickEvent event) {
				loadMyMarkets();
				
			}
		});
		marketPanel.add(marketFlexTable);
		
		mainPanel.add(marketPanel);
		blockTradeLabel.setVisible(false);
		mainPanel.add(blockTradeLabel);
		mainPanel.add(lastUpdatedLabel);
		DisclosurePanel blockTradePanel = createBlockTradePanel();
		mainPanel.add(blockTradePanel);
		//mainPanel.add(positionTable);
		DisclosurePanel myMarketsPanel = new DisclosurePanel("My Markets");
		VerticalPanel myMarketVerticalPanel = new VerticalPanel();
		myMarketVerticalPanel.add(refreshMyMarketsButton);
		myMarketVerticalPanel.add(myMarketsTable);
		myMarketsPanel.add(myMarketVerticalPanel);
		mainPanel.add(myMarketsPanel);
		
		
		RootPanel.get("marketList").add(mainPanel);
		loadCurrentTrader();
		loadMarkets();
		
		Timer refreshMarketsTimer = new Timer() {
	        @Override
	        public void run() {
	          refreshMarkets();
	        }

			
	      };
	      refreshMarketsTimer.scheduleRepeating(REFRESH_MARKET_INTERVAL);		
	}
	private void loadPositions() {
		if(nhlTraderPositionService == null){
			nhlTraderPositionService = GWT.create(NHLTraderPositionService.class);
		}
		nhlTraderPositionService.getPositionsForTrader(trader.getGoogleAccount(), new AsyncCallback<List<NHLTraderPosition>>() {
			
			@Override
			public void onSuccess(List<NHLTraderPosition> result) {
				int rowCount = 1;
				for (NHLTraderPosition nhlTraderPosition : result) {
//					if (rowCount % 2 == 0){
//						positionTable.getRowFormatter().addStyleName(rowCount, "marketEvenRows");	
//					}else{
//						positionTable.getRowFormatter().addStyleName(rowCount, "marketOddRows");
//					}
//					positionTable.setText(rowCount, 1,nhlTraderPosition.getTeam());
//					positionTable.setText(rowCount, 2,nhlTraderPosition.getPosition().toString());
					int indexOf = eastTeamIds.indexOf(nhlTraderPosition.getTeam())+1;
					marketFlexTable.setText(indexOf, 10, nhlTraderPosition.getPosition().toString());
					rowCount++;
				}
				
			}
			
			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}
		});
		
	}
	
	private DisclosurePanel createBlockTradePanel() {
		DisclosurePanel panelToReturn = new DisclosurePanel("Enter Block Trade");
		VerticalPanel mainPanel = new VerticalPanel();
		teams = new ListBox(false);
		traders = new ListBox(false);		
		buySell = new ListBox(false);
		buySell.addItem("Buy");
		buySell.addItem("Sell");
		sharesBox = new TextBox();
		sharesBox.setText("Shares");
		priceBox = new TextBox();
		priceBox.setText("Price");
		HorizontalPanel one = new HorizontalPanel();
		one.setSpacing(10);
		one.addStyleName("paddedHorizontalPanel");
		HorizontalPanel two = new HorizontalPanel();
		two.addStyleName("paddedHorizontalPanel");
		two.setSpacing(10);
		HorizontalPanel three = new HorizontalPanel();
		three.addStyleName("paddedHorizontalPanel");
		three.setSpacing(10);
		tradeButton = new Button("Trade");
		tradeButton.addClickHandler(new CreateBlockTradeClickHandler());
		one.add(new Label ("I "));
		one.add(buySell);
		one.add(new Label(" from/to "));
		one.add(traders);
		two.add(sharesBox);
		two.add(new Label(" of "));
		two.add(teams);
		three.add(new Label("for "));
		three.add(priceBox);
		three.add(tradeButton);
		mainPanel.add(one);
		mainPanel.add(two);
		mainPanel.add(three);
		panelToReturn.add(mainPanel);
		tradeButton.setEnabled(false);
		return panelToReturn;
	}
	
	private void refreshMarkets() {
		if (nhlMarketService == null){
			nhlMarketService = GWT.create(NHLMarketsService.class);
		}
		nhlMarketService.getMarkets(allTeams, new AsyncCallback<List<NHLMarket>>() {

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(List<NHLMarket> result) {
				for (NHLMarket nhlMarket : result) {
					int row = eastTeamIds.indexOf(nhlMarket.getTeam().getId())+1;
					Label hitLabel = new Label("Hit");
					Label liftLabel = new Label("Lift");
					Label currentBidLevel = new Label( nhlMarket.getBidLevel().toString());
					Label currentOfferLevel = new Label( nhlMarket.getAskLevel().toString());
					if (trader.isAuthorized()){
						hitLabel.addClickHandler(new ClickHitBidHandler(nhlMarket));
						liftLabel.addClickHandler(new ClickLiftOfferHandler(nhlMarket));
						currentBidLevel.addClickHandler(new AddBidClickHandler(nhlMarket));
						currentOfferLevel.addClickHandler(new AddOfferClickHandler(nhlMarket));
					}
					marketFlexTable.setWidget(row, 3, hitLabel);
					marketFlexTable.setText(row, 4, nhlMarket.getBidSize().toString());
					
					marketFlexTable.setWidget(row, 5, currentBidLevel);
					marketFlexTable.setWidget(row, 6, currentOfferLevel);
					marketFlexTable.setText(row, 7, nhlMarket.getAskSize().toString());
					marketFlexTable.setWidget(row, 8, liftLabel);
					marketFlexTable.setText(row, 9, nhlMarket.getLastTrade().toString());
				}
				 lastUpdatedLabel.setText("Last update : " + DateTimeFormat.getMediumDateTimeFormat().format(new Date()));
				 loadPositions();
			}

			
		});
		
	}
	
	private void loadMyMarkets() {
		refreshMyMarketsButton.setEnabled(false);
		refreshMyMarketsButton.setText("Refreshing");
		if (nhlMarketService == null){
			nhlMarketService = GWT.create(NHLMarketsService.class);
		}
		nhlMarketService.getMyMarkets(trader.getGoogleAccount(), new AsyncCallback<List<NHLBidASk>>() {

			@Override
			public void onFailure(Throwable caught) {
				refreshMyMarketsButton.setEnabled(true);
				refreshMyMarketsButton.setText("Refresh my markets");
			}

			@Override
			public void onSuccess(List<NHLBidASk> result) {
				myMarketsTable.removeAllRows();
				myMarketsTable.getRowFormatter().addStyleName(0, "watchListHeader");
				myMarketsTable.setText(0, 0, "Kill");
				myMarketsTable.setText(0, 1, "b/o");
				myMarketsTable.setText(0, 2, "Team");
				myMarketsTable.setText(0, 3, "Level");
				myMarketsTable.setText(0, 4, "Volume");
				
				int rowCount = 1;
				for (NHLBidASk nhlBidASk : result) {
					Button button = new Button("Kill");
					KillBidAskClickHandler clickHandler = new KillBidAskClickHandler(nhlBidASk.getId(), button);
					button.addClickHandler(clickHandler);
					myMarketsTable.setWidget(rowCount, 0, button);
					
					Integer volume = nhlBidASk.getVolume();
					if (rowCount % 2 == 0){
						myMarketsTable.getRowFormatter().addStyleName(rowCount, "marketEvenRows");	
					}else{
						myMarketsTable.getRowFormatter().addStyleName(rowCount, "marketOddRows");
					}
					
					if (nhlBidASk.getVolume()<0){
						myMarketsTable.setText(rowCount, 1,"Offer");
						volume = volume*-1;
						myMarketsTable.setText(rowCount, 4, volume.toString());
					}else{
						myMarketsTable.setText(rowCount, 1, "Bid");
						myMarketsTable.setText(rowCount, 4, volume.toString());
						
					}
					myMarketsTable.setText(rowCount, 2, nhlBidASk.getTeam().getId());
					myMarketsTable.setText(rowCount, 3, nhlBidASk.getPrice().toString());
					rowCount++;
				}
				refreshMyMarketsButton.setEnabled(true);
				refreshMyMarketsButton.setText("Refresh my markets");
			}
		});
		
	}

	private void loadMarkets() {
		if (nhlTeamService == null){
			nhlTeamService = GWT.create(NHLTeamService.class);
		}
		nhlTeamService.getAllTeams(new AsyncCallback<List<NHLTeam>>() {

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(List<NHLTeam> result) {
				
				for (NHLTeam nhlTeam : result) {
						allTeams.add(nhlTeam);
						eastTeamIds.add(nhlTeam.getId());
						int rowCount = marketFlexTable.getRowCount();
						Image logo = new Image(new StringBuilder().append("images/").append(nhlTeam.getId().toLowerCase()).append(".png").toString());
						if (rowCount % 2 == 0){
							marketFlexTable.getRowFormatter().addStyleName(rowCount, "marketEvenRows");	
						}else{
							marketFlexTable.getRowFormatter().addStyleName(rowCount, "marketOddRows");
						}
						marketFlexTable.setWidget(rowCount, 0, logo);
						marketFlexTable.setText(rowCount, 1, nhlTeam.getCity());
						marketFlexTable.getCellFormatter().addStyleName(rowCount, 3, "hitBidCell");
						marketFlexTable.getCellFormatter().addStyleName(rowCount, 8, "liftOfferCell");
						marketFlexTable.getCellFormatter().addStyleName(rowCount,5, "addBidOrOffer");
						marketFlexTable.getCellFormatter().addStyleName(rowCount, 6, "addBidOrOffer");
						String  hubLabel = (nhlTeam.getConference().equalsIgnoreCase("W")) ? "West" : "East";
						marketFlexTable.setText(rowCount, 2, hubLabel);
						teams.addItem(nhlTeam.getCity(),nhlTeam.getId());
				}
				loadMyMarkets();
				refreshMarkets();
			}
		});
		
		
		
	}
	private void loadCurrentTrader() {
		if (nhlTraderServiceAsync == null){
			nhlTraderServiceAsync = GWT.create(NHLTraderService.class);
		}
		nhlTraderServiceAsync.getTraderWithGoogleAccount(loginInfo.getEmailAddress(), new AsyncCallback<NHLTrader>() {

			@Override
			public void onFailure(Throwable caught) {
				
			}

			@Override
			public void onSuccess(NHLTrader traderFromService) {
				trader = traderFromService;
				if (trader.isAuthorized()){
					tradeButton.setEnabled(true);
				}
				welcomeLabel.setText(new StringBuilder().append(REFRESH_MARKET_INTERVAL).append(" Welcome back ").append(traderFromService.getAlias()).toString());
			}
			
		});
		nhlTraderServiceAsync.getAllTraders(new AsyncCallback<List<NHLTrader>>() {

			@Override
			public void onFailure(Throwable caught) {
				
				
			}

			@Override
			public void onSuccess(List<NHLTrader> result) {
				for (NHLTrader nhlTrader : result) {
					traders.addItem(nhlTrader.getAlias(),nhlTrader.getGoogleAccount());
					traderMap.put(nhlTrader.getGoogleAccount(), nhlTrader);
				}
				
			}
		});
		
	}
	//This is where the actions and click handlers starts
	class ClickHitBidHandler implements ClickHandler{
		private NHLMarket result;

		public ClickHitBidHandler(NHLMarket market) {
			this.result = market;
		}
		
		@Override
		public void onClick(ClickEvent event) {
			DialogBox hitDialog = createHitDialog( result);
			hitDialog.setPopupPosition(event.getClientX(), event.getClientY());
			hitDialog.setAnimationEnabled(true);
			hitDialog.setVisible(true);
			hitDialog.show();
		}
		
	}
	class ClickLiftOfferHandler implements ClickHandler{
		private NHLMarket market;
		
		public ClickLiftOfferHandler(NHLMarket market) {
			this.market = market;
		}
		
		@Override
		public void onClick(ClickEvent event) {
			DialogBox liftDialog = createLiftDialogBox(market);
			liftDialog.setPopupPosition(event.getClientX(), event.getClientY());
			liftDialog.setAnimationEnabled(true);
			liftDialog.setVisible(true);
			liftDialog.show();
		}
		
	}
	class AddBidClickHandler implements ClickHandler{
		
		private final NHLMarket market;

		public AddBidClickHandler(NHLMarket market) {
			this.market = market;
		}

		@Override
		public void onClick(ClickEvent event) {
			DialogBox hitDialog = createAddBidDialog(market);
			hitDialog.setPopupPosition(event.getClientX(), event.getClientY());
			hitDialog.setAnimationEnabled(true);
			hitDialog.setVisible(true);
			hitDialog.show();
		}
		
	}
	class AddOfferClickHandler implements ClickHandler{
		
		private final NHLMarket market;

		public AddOfferClickHandler(NHLMarket market) {
			this.market = market;
			
		}

		@Override
		public void onClick(ClickEvent event) {
			
			DialogBox hitDialog = createAddOfferDialog(market);
			hitDialog.setPopupPosition(event.getClientX(), event.getClientY());
			hitDialog.setAnimationEnabled(true);
			hitDialog.setVisible(true);
			hitDialog.show();
		}
		
	}
	private DialogBox createAddBidDialog(NHLMarket market) {
	  final DialogBox box = new  DialogBox();
	  VerticalPanel mainPanel = new VerticalPanel();
	  Label title = new Label("Add Bid for " + market.getTeam().getCity());
	  
	  mainPanel.add(title);
	  TextBox volumeBox = new TextBox();
	  TextBox priceBox = new TextBox();
	  
	  HorizontalPanel pricePanel = new HorizontalPanel();
	  HorizontalPanel volumePanle = new HorizontalPanel();
	  pricePanel.add(new Label("Price: "));
	  pricePanel.add(priceBox);
	  volumePanle.add(new Label("Size: "));
	  volumePanle.add(volumeBox);
	  mainPanel.add(pricePanel);
	  mainPanel.add(volumePanle);
	  Label errorMsgLabel = new Label();
	  errorMsgLabel.setStyleName("errorMessage");
	  errorMsgLabel.setVisible(false);
	  mainPanel.add(errorMsgLabel);
	  Button closeButton = new Button("Cancel",new CloseDialog(box));
	  HorizontalPanel buttonPanel = new HorizontalPanel();
	  Button button = new Button("Add Bid");
	  button.addClickHandler(new CreateBidClickHandler(market, volumeBox, priceBox,box,errorMsgLabel, button));
	  buttonPanel.add(button);
	  buttonPanel.add(closeButton);
	  mainPanel.add(buttonPanel);
	  box.add(mainPanel);
	  return box;
	}
	private DialogBox createHitDialog(NHLMarket market) {
		
		final DialogBox box = new  DialogBox();
		VerticalPanel mainPanel = new VerticalPanel();
		box.setTitle("Hit Bid");
		Label teamLabel = new Label("Sell block(5) shares " + market.getTeam().getCity() + " $"+market.getBidLevel());
		mainPanel.add(teamLabel);
		HorizontalPanel panel = new HorizontalPanel();
		panel.add(new Label("Size"));
		mainPanel.add(panel);
		Button closeButton = new Button("Close",new CloseDialog(box));
		HorizontalPanel buttonPanel = new HorizontalPanel();
		Button hitButton = new Button("Hit");
		hitButton.addClickHandler(new HitBidClickHandler(market,box,hitButton));
		buttonPanel.add(hitButton);
		buttonPanel.add(closeButton);
		mainPanel.add(buttonPanel);
		box.add(mainPanel);
		return box;
	}
	class HitBidClickHandler implements ClickHandler{

		private NHLMarket market;
		private DialogBox dialog;
		private final Button button;

		public HitBidClickHandler(NHLMarket market, DialogBox dialog, Button button) {
			this.market = market;
			this.dialog = dialog;
			this.button = button;
		}

		@Override
		public void onClick(ClickEvent event) {
			button.setText("Hitting");
			button.setEnabled(false);
			market.hitBid(trader.getGoogleAccount());
			nhlMarketService.processHitLift(trader,market, new AsyncCallback<NHLTradeEntryDto>() {
				
				@Override
				public void onSuccess(NHLTradeEntryDto dto) {
					refreshMarkets();
					button.setText("Hit");
					button.setEnabled(true);
					dialog.hide();
					NHLTrader buyer = traderMap.get(dto.getBuyer().getGoogleAccount());
					NHLTrader seller = traderMap.get(dto.getSeller().getGoogleAccount());
					String buyLabelString = new StringBuffer().append(buyer.getAlias()).append(" BUYS").toString();
					String sellLabelString = new StringBuffer().append(seller.getAlias()).append(" SELLS").toString();
					String summary = new StringBuffer().append(dto.getShares().toString()).append(" of ").append(dto.getTeamId()).append(" @ $").append(dto.getPrice().toString()).toString();
					String string = new StringBuffer().append(buyLabelString).append(" ").append(sellLabelString).append(" ").append(summary).toString();
					blockTradeLabel.setStyleName("successMessage");
					blockTradeLabel.setText(string);
					blockTradeLabel.setVisible(true);
					blockTradeLabel.addClickHandler(new ClickHandler(){
						@Override
						public void onClick(ClickEvent event) {
							blockTradeLabel.setText("");
							blockTradeLabel.setVisible(false);
						}
					});
					loadMyMarkets();
				}
				
				@Override
				public void onFailure(Throwable caught) {
					blockTradeLabel.setStyleName("errorMessage");
					blockTradeLabel.setText(caught.getMessage());
					blockTradeLabel.setVisible(true);
					blockTradeLabel.addClickHandler(new ClickHandler(){
						@Override
						public void onClick(ClickEvent event) {
							blockTradeLabel.setText("");
							blockTradeLabel.setVisible(false);
						}
					});
					
				}
			});
		}
		
	}
	
	
	
	
	private DialogBox createAddOfferDialog(NHLMarket market) {
		final DialogBox box = new  DialogBox();
		VerticalPanel mainPanel = new VerticalPanel();
		Label title = new Label("Add Offer for " + market.getTeam().getCity());
		
		mainPanel.add(title);
		TextBox volumeBox = new TextBox();
		TextBox priceBox = new TextBox();
		
		HorizontalPanel pricePanel = new HorizontalPanel();
		HorizontalPanel volumePanle = new HorizontalPanel();
		pricePanel.add(new Label("Price: "));
		pricePanel.add(priceBox);
		volumePanle.add(new Label("Size: "));
		volumePanle.add(volumeBox);
		mainPanel.add(pricePanel);
		mainPanel.add(volumePanle);
		Label errorLabel = new Label();
		errorLabel.setVisible(false);
		mainPanel.add(errorLabel);
		Button closeButton = new Button("Cancel",new CloseDialog(box));
		HorizontalPanel buttonPanel = new HorizontalPanel();
		Button button = new Button("Add Offer");
		button.addClickHandler(new CreateOfferClickHandler(market, volumeBox, priceBox,box,errorLabel,button));
		buttonPanel.add(button);
		buttonPanel.add(closeButton);
		mainPanel.add(buttonPanel);
		box.add(mainPanel);
		return box;
	}
	
	
	private DialogBox createLiftDialogBox(NHLMarket market) {
		final DialogBox box = new  DialogBox();
		VerticalPanel mainPanel = new VerticalPanel();
		box.setTitle("Lift Offer");
		Label teamLabel = new Label("Buy block(5) shares " + market.getTeam().getCity() + " $"+market.getAskLevel());
		mainPanel.add(teamLabel);
		HorizontalPanel panel = new HorizontalPanel();
		panel.add(new Label("Size"));
		mainPanel.add(panel);
		Button closeButton = new Button("Close",new CloseDialog(box));
		HorizontalPanel buttonPanel = new HorizontalPanel();
		Button liftButton = new Button("Lift");
		liftButton.addClickHandler(new LiftOfferClickHandler(market,box,liftButton));
		buttonPanel.add(liftButton);
		buttonPanel.add(closeButton);
		mainPanel.add(buttonPanel);
		box.add(mainPanel);
		return box;
	}
	class LiftOfferClickHandler implements ClickHandler{
		
		private NHLMarket market;
		private DialogBox dialog;
		private final Button button;
		
		public LiftOfferClickHandler(NHLMarket market, DialogBox dialog, Button button) {
			this.market = market;
			this.dialog = dialog;
			this.button = button;
		}
		
		@Override
		public void onClick(ClickEvent event) {
			market.liftOffer(trader.getGoogleAccount());
			nhlMarketService.processHitLift(trader,market, new AsyncCallback<NHLTradeEntryDto>() {
				
				@Override
				public void onSuccess(NHLTradeEntryDto dto) {
					refreshMarkets();
					button.setText("Hit");
					button.setEnabled(true);
					dialog.hide();
					NHLTrader buyer = traderMap.get(dto.getBuyer().getGoogleAccount());
					NHLTrader seller = traderMap.get(dto.getSeller().getGoogleAccount());
					String buyLabelString = new StringBuffer().append(buyer.getAlias()).append(" BUYS").toString();
					String sellLabelString = new StringBuffer().append(seller.getAlias()).append(" SELLS").toString();
					String summary = new StringBuffer().append(dto.getShares().toString()).append(" of ").append(dto.getTeamId()).append(" @ $").append(dto.getPrice().toString()).toString();
					String string = new StringBuffer().append(buyLabelString).append(" ").append(sellLabelString).append(" ").append(summary).toString();
					blockTradeLabel.setStyleName("successMessage");
					blockTradeLabel.setText(string);
					blockTradeLabel.setVisible(true);
					blockTradeLabel.addClickHandler(new ClickHandler(){
						@Override
						public void onClick(ClickEvent event) {
							blockTradeLabel.setText("");
							blockTradeLabel.setVisible(false);
						}
					});
					loadMyMarkets();
					
				}
				
				@Override
				public void onFailure(Throwable caught) {
					blockTradeLabel.setStyleName("errorMessage");
					blockTradeLabel.setText(caught.getMessage());
					blockTradeLabel.setVisible(true);
					blockTradeLabel.addClickHandler(new ClickHandler(){
						@Override
						public void onClick(ClickEvent event) {
							blockTradeLabel.setText("");
							blockTradeLabel.setVisible(false);
						}
					});
					
				}
			});
		}
		
	}
	
	public FlexTable getPositionTable() {
		return positionTable;
	}
	public void setPositionTable(FlexTable positionTable) {
		this.positionTable = positionTable;
	}
	
	

	class CreateBidClickHandler implements ClickHandler{
		private final NHLMarket market;
		private final TextBox volumeTextBox;
		private final TextBox priceTextBox;
		private final DialogBox box;
		private Label errorLabel;
		private final Button button;

		public CreateBidClickHandler(NHLMarket market, TextBox volume, TextBox price, DialogBox box, Label errorLabel, Button button) {
			this.market = market;
			this.volumeTextBox = volume;
			this.priceTextBox = price;
			this.box = box;
			this.errorLabel = errorLabel;
			this.button = button;
			
		}

		@Override
		public void onClick(ClickEvent event) {
			button.setText("adding...");
			button.setEnabled(false);
			Integer volume = new Integer(volumeTextBox.getValue().toString());
			Double price = new Double(priceTextBox.getValue().toString());
			NHLBidASk newBidAsk = new NHLBidASk();
			newBidAsk.setPrice(price);
			newBidAsk.setVolume(volume);
			newBidAsk.setTeam(market.getTeam());
			newBidAsk.setTraderId(trader.getGoogleAccount());
			nhlMarketService.insertBidAsk(newBidAsk, new AsyncCallback<NHLBidASk>() {
				
				@Override
				public void onSuccess(NHLBidASk result) {
					refreshMarkets();
					loadMyMarkets();
					box.hide();
					
				}
				
				@Override
				public void onFailure(Throwable caught) {
					errorLabel.setVisible(true);
					errorLabel.setText("Odd Lot Exception:  Bids and Offers are to be in lots of 5");
					
				}
			});
		}
		
	}
	class CreateOfferClickHandler implements ClickHandler{
		private final NHLMarket market;
		private final TextBox volumeTextBox;
		private final TextBox priceTextBox;
		private final DialogBox box;
		private Label errorLabel;
		private Button button;
		
		public CreateOfferClickHandler(NHLMarket market, TextBox volume, TextBox price, DialogBox box, Label errorMessage, Button button) {
			this.market = market;
			this.volumeTextBox = volume;
			this.priceTextBox = price;
			this.box = box;
			this.errorLabel = errorMessage;
			this.button = button;
			
		}
		
		@Override
		public void onClick(ClickEvent event) {
			button.setText("adding...");
			button.setEnabled(false);
			Integer volume = new Integer(volumeTextBox.getValue().toString());
			volume = volume*-1;
			Double price = new Double(priceTextBox.getValue().toString());
			NHLBidASk newBidAsk = new NHLBidASk();
			newBidAsk.setPrice(price);
			newBidAsk.setVolume(volume);
			newBidAsk.setTeam(market.getTeam());
			newBidAsk.setTraderId(trader.getGoogleAccount());
			nhlMarketService.insertBidAsk(newBidAsk, new AsyncCallback<NHLBidASk>() {
				
				@Override
				public void onSuccess(NHLBidASk result) {
					refreshMarkets();
					loadMyMarkets();
					box.hide();
				}
				
				@Override
				public void onFailure(Throwable caught) {
					errorLabel.setVisible(true);
					errorLabel.setText("Odd Lot Exception:  Bids and Offers are to be in lots of 5");
					
				}
			});
			
		}
		
	}
	class CreateBlockTradeClickHandler implements ClickHandler{
		@Override
		public void onClick(ClickEvent event) {			
			tradeButton.setEnabled(false);
			tradeButton.setText("Executing Trade");
			
			NHLTradeEntryDto newTrade = new NHLTradeEntryDto(); 
			String buySellValue = buySell.getValue(buySell.getSelectedIndex());
			newTrade.setPrice(new Double(priceBox.getValue()));
			newTrade.setShares(new Integer(sharesBox.getValue()));
			if (buySellValue.equalsIgnoreCase("buy")){				newTrade.setBuyer(trader);
				String seller = traders.getValue(traders.getSelectedIndex());
				newTrade.setSeller(traderMap.get(seller));
			}else{
				newTrade.setSeller(trader);
				String buyer = traders.getValue(traders.getSelectedIndex());
				newTrade.setBuyer(traderMap.get(buyer));
			}
			String teamId = teams.getValue(teams.getSelectedIndex());
			newTrade.setTeamId(teamId);
			
			nhlMarketService.saveTrade(newTrade, new AsyncCallback<NHLTradeEntryDto>() {
				
				@Override
				public void onFailure(Throwable caught) {
					System.out.println("Fail");
					
				}
				@Override
				public void onSuccess(NHLTradeEntryDto dto) {
					String buyLabelString = new StringBuffer().append(dto.getBuyer().getAlias()).append(" BUYS").toString();
					String sellLabelString = new StringBuffer().append(dto.getSeller().getAlias()).append(" SELLS").toString();
					String summary = new StringBuffer().append(dto.getShares().toString()).append(" @ $").append(dto.getPrice().toString()).toString();
					String string = new StringBuffer().append(buyLabelString).append(" ").append(sellLabelString).append(" ").append(summary).toString();
					blockTradeLabel.setText(string);
					tradeButton.setEnabled(true);
					tradeButton.setText("Trade");
					sharesBox.setText("Shares");
					priceBox.setText("Price");
				}
			});
			
		}
	}
	class KillBidAskClickHandler implements ClickHandler{
		private final Integer bidAskId;
		private final Button button;
		

		public KillBidAskClickHandler(Integer bidAskId, Button button) {
			this.bidAskId = bidAskId;
			this.button = button;
		}

		@Override
		public void onClick(ClickEvent event) {
				button.setEnabled(false);
				button.setText("Killing...");
				nhlMarketService.killBidAsk(bidAskId, new AsyncCallback<Boolean>() {
				@Override
				public void onFailure(Throwable caught) {
					blockTradeLabel.setStyleName("errorMessage");
					blockTradeLabel.setText(caught.getMessage());
					blockTradeLabel.setVisible(true);
					blockTradeLabel.addClickHandler(new ClickHandler(){
						@Override
						public void onClick(ClickEvent event) {
							blockTradeLabel.setText("");
							blockTradeLabel.setVisible(false);
						}
					});
					refreshMarkets();
					loadMyMarkets();
					
				}

				@Override
				public void onSuccess(Boolean result) {
					refreshMarkets();
					loadMyMarkets();
				}
			});
			
		}	
	}
	
	
}
